package the.workshop.milktea.service;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.wisteria.framework.web.mvc.service.AbstractSuperService;
import the.workshop.milktea.infrastructure.mapper.TeaShopMapper;
import the.workshop.milktea.infrastructure.model.Device;
import the.workshop.milktea.infrastructure.model.Shop;
import the.workshop.milktea.service.dto.ShopAddDTO;
import the.workshop.milktea.service.dto.ShopDeviceSubDTO;
import the.workshop.milktea.service.dto.ShopGetDTO;
import the.workshop.milktea.service.dto.ShopModifyDTO;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * <p>
 * 种类 服务实现类
 * </p>
 *
 * @author huamu
 * @since 2023-04-01
 */
@Service
public class TeaShopService extends AbstractSuperService<TeaShopMapper, Shop> {

    @Resource
    private DeviceService deviceService;

    public boolean add(ShopAddDTO dto) {
        Shop entity = new Shop();
        BeanUtils.copyProperties(dto, entity);

        entity.setCreatedId(dto.getOperatorId());
        entity.setCreatedName(dto.getOperatorName());
        entity.setCreatedTime(new Date());
        entity.setModifiedId(dto.getOperatorId());
        entity.setModifiedName(dto.getOperatorName());
        entity.setModifiedTime(new Date());
        this.baseMapper.insert(entity);

        if (!CollectionUtils.isEmpty(dto.getDeviceIdList())) {
            List<Device> deviceList = new ArrayList<>();
            Device device = null;
            for (Integer deviceId : dto.getDeviceIdList()) {
                device = new Device();
                device.setId(deviceId);
                device.setShopId(entity.getId());
                device.setModifiedTime(new Date());
                device.setModifiedId(dto.getOperatorId());
                device.setModifiedName(dto.getOperatorName());
                deviceList.add(device);
            }
            deviceService.updateBatchById(deviceList);
        }

        return true;
    }

    public boolean modify(ShopModifyDTO dto) {
        Shop entity = new Shop();
        BeanUtils.copyProperties(dto, entity);
        entity.setId(dto.getShopId());

        entity.setModifiedId(dto.getOperatorId());
        entity.setModifiedName(dto.getOperatorName());
        entity.setModifiedTime(new Date());
        this.baseMapper.updateById(entity);

        deviceService.update(new LambdaUpdateWrapper<Device>()
                .set(Device::getShopId, null)
                .set(Device::getModifiedTime, new Date())
                .set(Device::getModifiedName, dto.getOperatorName())
                .set(Device::getModifiedId, dto.getOperatorId())

                .eq(Device::getShopId, entity.getId())
        );
        if (!CollectionUtils.isEmpty(dto.getDeviceIdList())) {
            List<Device> deviceList = new ArrayList<>();
            Device device = null;
            for (Integer deviceId : dto.getDeviceIdList()) {
                device = new Device();
                device.setId(deviceId);
                device.setShopId(entity.getId());
                device.setModifiedTime(new Date());
                device.setModifiedId(dto.getOperatorId());
                device.setModifiedName(dto.getOperatorName());
                deviceList.add(device);
            }
            deviceService.updateBatchById(deviceList, deviceList.size());
        }
        return true;
    }

    public ShopGetDTO get(Integer shopId) {
        Shop entity = this.baseMapper.selectById(shopId);
        if (entity == null) {
            return null;
        }

        List<Device> deviceList = deviceService.list(new LambdaQueryWrapper<Device>()
                .eq(Device::getShopId, shopId)
        );
        ShopGetDTO dto = new ShopGetDTO();
        BeanUtils.copyProperties(entity, dto);
        dto.setShopId(entity.getId());
        if (!CollectionUtils.isEmpty(deviceList)) {
            dto.setDeviceList(deviceList.stream().map(this::convertOf).collect(Collectors.toList()));
        }

        return dto;
    }

    private ShopDeviceSubDTO convertOf(Device source) {
        ShopDeviceSubDTO target = new ShopDeviceSubDTO();
        target.setDeviceId(source.getId());
        target.setMac(source.getMac());
        target.setLockStatus(source.getLockStatus());
        return target;
    }
}
